#include <iostream>
#include <unistd.h>
#include <functional>
#include <pthread.h>
#include <sys/types.h>
#include <unistd.h>
#include <time.h>
#include <vector>


// //////1.创建两个线程，编译时需要引入线程库
// //新线程
// void *ThreadRountine(void *args)
// {
//     while(true)
//     {
//         std::cout << "new thread" << std::endl;
//         sleep(1);
//     }
// }

// //主线程
// int main()
// {
//     pthread_t tid;
//     pthread_create(&tid, NULL, ThreadRountine, NULL);
//     while(true)
//     {
//         std::cout << "main thread" << std::endl;
//         sleep(1);
//     }
//     return 0;
// }



////2.如何给线程传参
//typedef std::function<void()> func_t;
// using func_t = std::function<void()>;.
// void Print()
// {
//     std::cout << "我是线程执行大任务的一部分" << std::endl;
// }

// class ThreadData
// {
// public:
//       ThreadData(const std::string &name, const int16_t &ctime, func_t f)
//       :threadname(name), createtime(ctime), func(f)
//       {}

// public:
//     std::string threadname;
//     int createtime;
//     func_t func;
// };



// //新线程
// void *ThreadRountine(void *args)
// {
//     ThreadData *td = static_cast<ThreadData*>(args);
//     while(true)
//     {
//         std::cout << "new thread"  << "thread name: " << td->threadname <<"creat time: " << td->createtime  << std::endl;
//         td->func();
//         sleep(1);
//     }
// }


// int main()
// {
//     pthread_t tid;
//     ThreadData *td = new ThreadData("thread 1", (uint64_t)time(NULL), Print);
//     pthread_create(&tid, NULL, ThreadRountine, td);
//     while(true)
//     {
//         std::cout << "main thread" << std::endl;
//         sleep(1);
//     }
// }


////3.创建多线程
/////研究两个问题：（1）线程的健壮性问题,一个出问题会影响其他的 （2）观察一下thread id

using func_t = std::function<void()>;

const int threadnum = 5;
void Print()
{
    std::cout << "我是线程执行大任务的一部分" << std::endl;
}

class ThreadData
{
public:
      ThreadData(const std::string &name, const int16_t &ctime, func_t f)
      :threadname(name), createtime(ctime), func(f)
      {}

public:
    std::string threadname;
    int createtime;
    func_t func;
};



//新线程
void *ThreadRountine(void *args)
{
    ThreadData *td = static_cast<ThreadData*>(args);
    while(true)
    {
        std::cout << "new thread"  << "thread name: " << td->threadname <<" creat time: " << td->createtime  << std::endl;
        td->func();
        sleep(1);
    }
}


int main()
{
    //pthread_t tid;
    std::vector<pthread_t> pthreads;
    for(size_t i = 0; i < threadnum; i++)
    {
        char threadname[64];
        snprintf(threadname, sizeof(threadname), "%s-%lu", "thread", i);
        pthread_t tid;
        ThreadData *td = new ThreadData(threadname, (uint64_t)time(NULL), Print);
        pthread_create(&tid, NULL, ThreadRountine, td);
        pthreads.push_back(tid);
        sleep(1);

    }

    std::cout << "thread id: ";
    for(const auto &tid: pthreads)
    {
        std::cout << tid << ",";
    }
    
    std::cout << std::endl;
    while(true)
    {
        std::cout << "main thread" << std::endl;
        sleep(1);
    }
}



// //////1.创建两个线程，编译时需要引入线程库，查看线程id
// //新线程
// //thread id 本质上是一个地址/标识线程唯一性
// void *ThreadRountine(void *args)
// {
//     std::string name = static_cast<const char*>(args);
//     while(true)
//     {
//         std::cout << "new thread is running, thread name: " << name << "thread id: " << pthread_self() << std::endl;
//         sleep(1);
//     }
// }

// //主线程
// int main()
// {
//     pthread_t tid;
//     pthread_create(&tid, NULL, ThreadRountine, (void*)"thread-1");
//     //tid是输出型参数，是新线程的id
//     while(true)
//     {
//         std::cout << "main thread: "  << " main thread id: " << pthread_self() << std::endl;
//         sleep(1);
//     }
//     return 0;
// }

// //////创建两个线程，编译时需要引入线程库，查看线程id
// //新线程
// //线程终止
// void *ThreadRountine(void *args)
// {
//     std::string name = static_cast<const char*>(args);
//     int cnt = 5;
//     while(cnt--)
//     {
//         std::cout << "new thread is running, thread name: " << name << "thread id: " << pthread_self() << std::endl;
//         sleep(1);
//     }
//     //return nullptr;//1.线程终止
//    // exit(13);//2.进程终止
//     pthread_exit(nullptr);
// }

// //主线程
// int main()
// {
//     pthread_t tid;
//     pthread_create(&tid, NULL, ThreadRountine, (void*)"thread-1");
//     //tid是输出型参数，是新线程的id
//     while(true)
//     {
//         std::cout << "main thread: "  << " main thread id: " << pthread_self() << std::endl;
//         sleep(1);
//     }

//     //线程默认要被等待！
//     //1.线程退出，没有等待，会导致类似进程的僵尸问题
//     //2.线程退出时，主线程如何获取新线程的返回值



//     return 0;
// }


//////创建两个线程，编译时需要引入线程库，查看线程id
//新线程
//线程终止
void *ThreadRountine(void *args)
{
    std::string name = static_cast<const char*>(args);
    int cnt = 5;
    while(cnt--)
    {
        std::cout << "new thread is running, thread name: " << name << "thread id: " << pthread_self() << std::endl;
        sleep(1);
    }
    //return nullptr;//1.线程终止
   // exit(13);//2.进程终止
    pthread_exit(nullptr);
}

//主线程
int main()
{
    pthread_t tid;
    pthread_create(&tid, NULL, ThreadRountine, (void*)"thread-1");
    //tid是输出型参数，是新线程的id
    std::cout << "main thread: "  << " main thread id: " << pthread_self() << std::endl;
    sleep(1);
    

    //线程默认要被等待！
    //1.线程退出，没有等待，会导致类似进程的僵尸问题
    //2.线程退出时，主线程如何获取新线程的返回值
    int n = pthread_join(tid, nullptr);//等待成功，返回值为0
    std::cout << "main thread done" << "n: " << n << std::endl;
    return 0;
}

